package com.hxx.widget

import org.junit.Test

/**
 * Example local unit test, which will execute on the development machine (host).
 *
 * See [testing documentation](http://d.android.com/tools/testing).
 */
class ExampleUnitTest {
    fun addition_isCorrect() {
        val string = "123456789\nabcd\n\nabc\n\n\n\n"
        applySpanIndex(string, 9, 16) { start, end ->
            assert(start == 0)
            assert(end == 20)
        }
        applySpanIndex(string, 10, 14) { start, end ->
            assert(start == 10)
            assert(end == 15)
        }
        applySpanIndex(string, 9, 14) { start, end ->
            assert(start == 0)
            assert(end == 15)
        }
        applySpanIndex(string, 11, 14) { start, end ->
            assert(start == 10)
            assert(end == 15)
        }
        applySpanIndex(string, 11, 11) { start, end ->
            assert(start == 10)
            assert(end == 15)
        }
        applySpanIndex(string, 0, 0) { start, end ->
            assert(start == 0)
            assert(end == 10)
        }
        applySpanIndex(string, 1, 1) { start, end ->
            assert(start == 0)
            assert(end == 10)
        }
        applySpanIndex(string, 2, 6) { start, end ->
            assert(start == 0)
            assert(end == 10)
        }
        applySpanIndex(string, 7, 11)
        { start, end ->
            assert(start == 0)
            assert(end == 15)
        }
        val string1 = "1\n"
        applySpanIndex(string1, 0, 0) { start, end ->
            assert(start == 0)
            assert(end == 2)
        }
        applySpanIndex(string1, 1, 1) { start, end ->
            assert(start == 0)
            assert(end == 2)
        }
    }
    @Test
    fun subSingleLine() {
        val source = "1234"
        applySpanIndex(source, 0, 0) { start, end ->
            assert(start == 0 && end == 4)
        }
    }
    @Test
    fun subParagraph() {
        val source = "1234567\n89ab\n\ncde"
        applySpanIndex(source, 8, 8) { start, end ->
            assert(start == 8 && end == 13)
        }
        applySpanIndex(source, 0, 0) { start, end ->
            assert(start == 0 && end == 8)
        }
        applySpanIndex(source, 7, 7) { start, end ->
            assert(start == 0 && end == 8)
        }
        applySpanIndex(source, 8, 8) { start, end ->
            assert(start == 8 && end == 13)
        }
        applySpanIndex(source, 7, 15) { start, end ->
            if (start == 0 && end != 8) {
                assert(false)
            }
            if (start == 8 && end != 13) {
                assert(false)
            }
            if (start == 15 && end != 18) {
                assert(false)
            }
        }
    }

    fun applySpanIndex(
        source: String,
        selectionStart: Int,
        selectionEnd: Int,
        apply: (Int, Int) -> Unit
    ) {
        var startIndex = selectionStart
        var endIndex = selectionEnd
        while (true) {
            if (startIndex == 0) break
            startIndex--
            if (source[startIndex] == '\n') {
                startIndex += 1
                break
            }
        }

        while (true) {
            if (endIndex == source.length) break
            if (source[endIndex] == '\n') {
                endIndex++
                break
            }
            endIndex++
        }
        var rangeStart = startIndex

        for (i in startIndex .. endIndex) {
            if (i == endIndex) {
                apply(rangeStart, i)
                break
            }
            if (source[i] == '\n') {
                apply(rangeStart, i + 1)
                rangeStart = i + 1
                if (i == endIndex - 1){
                    break
                }
            }
        }
    }
}